package org.bigjava.novelplatform.controller;

import cn.hutool.core.util.HexUtil;
import cn.hutool.core.util.StrUtil;
import lombok.extern.slf4j.Slf4j;
import org.bigjava.novelplatform.common.enums.ActionType;
import org.bigjava.novelplatform.common.enums.PathMapEnum;
import org.bigjava.novelplatform.common.enums.Subscribe;
import org.bigjava.novelplatform.common.enums.UserRole;
import org.bigjava.novelplatform.common.utils.R;
import org.bigjava.novelplatform.common.utils.StringUtils;
import org.bigjava.novelplatform.common.utils.UploadUtils;
import org.bigjava.novelplatform.entity.Browsing;
import org.bigjava.novelplatform.entity.ChapterSays;
import org.bigjava.novelplatform.mapper.BrowsingMapper;
import org.bigjava.novelplatform.service.UserService;
import org.bigjava.novelplatform.vo.*;
import org.hibernate.validator.constraints.Length;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;
import sun.net.www.http.HttpClient;

import javax.annotation.Resource;
import javax.servlet.http.HttpSession;
import javax.validation.constraints.Email;
import javax.validation.constraints.NotEmpty;
import java.io.File;
import java.io.IOException;
import java.nio.charset.StandardCharsets;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.text.DateFormat;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.List;
import java.util.Map;

import static org.bigjava.novelplatform.common.constant.NovelInfoConstant.*;
import static org.bigjava.novelplatform.common.exception.ExceptionCodeMessage.*;

/**
 * @author ykh
 * @create 2022-04-04 8:36
 */
@Slf4j
@Validated
@RestController
@RequestMapping("/api/user")
public class UserController {

    @Resource
    public UserService userService;




    /**
     * 重置密码
     * 流程：1发送验证码sendRegisterCode-->2重置密码
     * Content-Type:application/x-www-form-urlencoded
     *
     * @return
     */
    @PostMapping("/resetPasswords")
    public R resetPasswords(@Length(min = 6) @NotEmpty String newPassword, @NotEmpty String authCode, UserInfoVo user) {
        //新密码
        //验证码

        userService.resetPasswords(user.getId(), newPassword, authCode);
        return R.ok();
    }


    /**
     * 发送修改码
     *
     * @return
     */
    @GetMapping("/sendRePasCode")
    public R sendResetPasswordsCode(UserInfoVo user) {
        //发送邮箱
        if (userService.sendMailResetPasswords(user.getId())) {
            return R.ok();
            
        }
        return R.error(AUTH_CODE_FAIL);
    }

    /**
     * 发送修改邮箱的验证码
     * @param map
     * @param userInfoVo
     * @return
     */
    @PostMapping("/sendReplaceEmail")
    public R replaceMailbox(@RequestBody Map<String,String> map,UserInfoVo userInfoVo){
        String email = map.get("email");
        if (StringUtils.isEmpty(email)){
            R.error(NON_COMPLIANT_PARAMETERS);
        }
        userService.replaceMailbox(email,userInfoVo.getId());
        return R.ok();
    }

    /**
     * 查询书架
     */
    @GetMapping("/bookRack")
    public R selectBookRackList(@RequestParam(value = "group",
            required = false) String group, UserInfoVo user) {

        List<BookRackItemVo> books = userService.selectBookRackByUserId(user.getId(), group);

        return R.ok().setData(books);
    }

    /**
     * 书架新增书籍/添加分组
     *
     * @param bookIdList
     * @return
     */
    @PostMapping("/bookRack")
    public R addBookRack(@RequestParam(value = "group", required = false) String group,
                         @RequestBody List<Integer> bookIdList, UserInfoVo user) {
        userService.addBookRack(user.getId(), group, bookIdList);
        return R.ok();
    }

    /**
     * 查询用户的所有分组
     * @param user
     * @return
     */
    @GetMapping("/bookRack/group")
    public R selectGroup( UserInfoVo user){
        List<String> groups = userService.selectGroup(user.getId());
        return R.ok().setData(groups);
    }

    /**
     * 将书籍加入书架的情况
     * @param group
     * @param bookId
     * @param user
     * @return
     */
    @PostMapping("/bookRack/{bookId}")
    public R addOneBookRack(@RequestBody Map<String,String> group, @PathVariable("bookId") Integer bookId,
                            UserInfoVo user) {

        boolean isOk  = userService.updateBookRack(user.getId(), group.get("group"), bookId);
        if (isOk){
            return R.ok();
        }else {
            return R.error(ALREADY_EXISTS);
        }

    }

    /**
     * 将书籍从一个分组移动到另一个分组
     * //     * @param userId
     *
     * @param oldGroup    旧分组
     * @param targetGroup 目标分组
     * @param bookIdList  书籍id集合
     * @return
     */
    @PostMapping("/moveBookRack")
    public R moveBookRack(@RequestParam("oldGroup") String oldGroup,
                          @RequestParam("targetGroup") String targetGroup,
                          @RequestBody List<Integer> bookIdList, UserInfoVo user) {
        userService.moveBookRack(user.getId(), oldGroup, targetGroup, bookIdList);
        return R.ok();
    }


    /**
     * 删除书籍
     *
     * @param bookIdList
     * @return
     */
    @PostMapping("/removeBookRaBck")
    public R removeBookRack(@RequestBody List<Integer> bookIdList, UserInfoVo user) {
        userService.removeBookRack(user.getId(), bookIdList);
        return R.ok();
    }

    /**
     * 逻辑删除
     * @param bookIdList
     * @param user
     * @return
     */
    @PostMapping("/logicalDeletion")
    public R logicalDeletion(@RequestBody List<Integer> bookIdList, UserInfoVo user){
        userService.logicalDeletion(user.getId(), bookIdList);
        return R.ok();
    }

    /**
     * 置顶
     *
     * @param bookId
     */
    @PostMapping("/topping/{bookId}")
    public R topping(@PathVariable("bookId") Integer bookId, UserInfoVo user) {
        userService.topping(user.getId(), bookId);
        return R.ok();
    }

    /**
     * 修改订阅状态
     *
     * @param bookId
     * @param user
     * @return
     */
    @PostMapping("/subscribe/{bookId}")
    public R subscribe(@PathVariable("bookId") Integer bookId, UserInfoVo user) {
        boolean b = userService.UpdateSubscribeState(user.getId(), bookId);
        if (b){
            return R.ok().setData(Subscribe.SIGNING);
        }else{
            return R.ok().setData(Subscribe.NOT_SIGNING);
        }
    }


    /**
     * 排序，置顶时需要排序
     */
    @PostMapping("/bookSort")
    public R bookSort(@RequestParam("group") String group, @RequestBody List<Integer> bookIds, UserInfoVo user) {
        userService.bookSort(user.getId(), group, bookIds);
        return R.ok();
    }

    /**
     * 申请成为作者
     *
     * @param user
     * @return
     */
    @PostMapping("/becomeAnAuthor")
    public R becomeAnAuthor(HttpSession session, UserInfoVo user) {
        userService.becomeAnAuthor(user.getId());
        user.setType(UserRole.WRITER.toString());
        session.setAttribute(SESSION_USER,user);
        return R.ok().setData(user);
    }

    /**
     * 文件上传,和信息修改
     *
     * @param user
     * @return
     */
    @PostMapping("/updateUserInfo")
    public R updateUserInfo(@RequestParam(value = "nickName",required = false) String nickName,
                            @RequestPart(value = "headPortrait",required = false) MultipartFile multipartFile,
                            @RequestParam(value = "email",required = false) @Email String email,
                            @RequestParam(value = "code",required = false) String code,
                            UserInfoVo user) throws IOException, NoSuchAlgorithmException {
        String url = null;
        if(nickName != null || multipartFile != null || code != null){
            url = UploadUtils.upload(multipartFile, PathMapEnum.USER_HEAD);
            userService.updateUserInfoById(user.getId(), url ,nickName,email,code);
        }
        if(!StringUtils.isEmpty(nickName) && !user.getNickName().equals(nickName)){
            user.setNickName(nickName);
        }
        if(!StringUtils.isEmpty(url)){
            user.setHeadPortraitUrl(url);
        }
        return R.ok().setData(user);
    }


    /**
     * 根据用户动作类型，点赞/点踩，或取消点赞/取消点踩
     * @param user
     * @return
     */
    @GetMapping("/giveTheThumbsUp/{actionType}/{id}")
    public R giveTheThumbsUp(@PathVariable("actionType") String actionType , @PathVariable("id") Long id,@RequestParam(required = false)  ActionType oldType ,UserInfoVo user){
        ChapterSays chapterSays = userService.giveTheThumbsUp(user.getId(), id, actionType, oldType);
        return R.ok().setData(chapterSays);
    }


    /**
     * 加载用户的页面的的方法
     *
     *
     */

    @GetMapping("/userInquire")
    public R userInquire(UserInfoVo userInfoVo){

        UserInquireVo userInquireVo = userService.userInquire(userInfoVo.getId());

        return R.ok().setData(userInquireVo);
    }


    @GetMapping("/urInfo/{bookId}")
    public R userInquire(@PathVariable("bookId") Integer bookId ,UserInfoVo userInfoVo){

        SimpleBookRackVo simpleBookRackVo = userService.selectBookRackByUserIdAndBookId(bookId, userInfoVo.getId());

        return R.ok().setData(simpleBookRackVo);
    }

    /**
     * 保存本章说
     * @param map
     * @param user
     * @return
     */
    @PostMapping("insterChaterSays")
    public R insterChaterSays(
            @RequestBody Map<String, String> map,
                               UserInfoVo user){
        Integer paragraphLocation = Integer.valueOf(map.get("indexs"));
        Long chapterId = Long.valueOf(map.get("zhangjieid"));
        String content = map.get("textarea");
        ChapterSays chapterSays = new ChapterSays();
        chapterSays.setParagraphLocation(paragraphLocation);
        chapterSays.setChapterId(chapterId);
        chapterSays.setContent(content);
        chapterSays.setAddressorId( user.getId());
        //        生成一个现在的时间
        Date birthDate = new Date();
        chapterSays.setPublishTime(birthDate);

        System.out.println(chapterSays.getParagraphLocation());

        chapterSays = userService.insterChaterSays(chapterSays);
        return R.ok().setData(chapterSays);
    }



    /**
     * 保存本章说
     * @param map
     * @param user
     * @return
     */
    @PostMapping("insterChaterSayszipin")
    public R insterChaterSayszipin(
            @RequestBody Map<String, String> map,
            UserInfoVo user){
        Integer conversationTargetId = Integer.valueOf(map.get("indexdd"));
        Long chapterId = Long.valueOf(map.get("zhangjieid"));
        String content = map.get("inputsss");
        ChapterSays chapterSays = new ChapterSays();
        chapterSays.setConversationTargetId(conversationTargetId);
        chapterSays.setChapterId(chapterId);
        chapterSays.setContent(content);
        chapterSays.setAddressorId( user.getId());
        //        生成一个现在的时间
        Date birthDate = new Date();
        chapterSays.setPublishTime(birthDate);

        System.out.println(chapterSays.getParagraphLocation());

        chapterSays = userService.insterChaterSays(chapterSays);
        return R.ok().setData(chapterSays);
    }


    /**
     * 保存的浏览记录
     * @param chapterId
     * @return
     */
    @GetMapping("/savethebrowse/{chapterId}/{bookId}")
    public R savethebrowse(@PathVariable("chapterId") Long chapterId,@PathVariable("bookId")Integer bookId,UserInfoVo user){
        Browsing browsing = new Browsing();
        browsing.setUserId(user.getId());
        //        生成一个现在的时间
        Date birthDate = new Date();
        browsing.setBrowsingTime(birthDate);
//       //传入的是章节id
        browsing.setBrowsingId(chapterId);

        userService.Savethebrowse(browsing,bookId);

        return R.ok();
    }




    /**
     * 查询的浏览记录
     * @return
     */
    @GetMapping("/selectbrowse/{bookId}")
    public R selectbrowse(@PathVariable("bookId")Integer bookId,UserInfoVo user){
        Integer integer = userService.selectChapters(bookId, user.getId());
        return R.ok().setData(integer);
    }

}



